<template>
  <q-page class="q-pa-md">
    <!-- 查询表单 -->
    <q-card flat bordered class="q-mb-md" v-if="state.search">
      <q-slide-transition>
        <q-card-section>
          <q-form @submit.prevent="handleQuery" class="row q-col-gutter-md">
            <!-- 查询字段 -->
            <q-input
              v-model.trim="queryParams.name"
              label="角色名称"
              outlined
              dense
              clearable
              class="col-md-3 col-sm-6 col-xs-12"
              @keyup.enter="handleQuery"
            >
              <template v-slot:prepend>
                <q-icon name="badge" />
              </template>
            </q-input>

            <q-input
              v-model.trim="queryParams.key"
              label="角色标识"
              outlined
              dense
              clearable
              class="col-md-3 col-sm-6 col-xs-12"
              @keyup.enter="handleQuery"
            >
              <template v-slot:prepend>
                <q-icon name="vpn_key" />
              </template>
            </q-input>

            <q-select
              v-model="queryParams.status"
              label="状态"
              :options="statusOptions"
              outlined
              dense
              clearable
              emit-value
              map-options
              class="col-md-3 col-sm-6 col-xs-12"
              @keyup.enter="handleQuery"
            >
              <template v-slot:prepend>
                <q-icon name="toggle_on" />
              </template>
            </q-select>

            <!-- 操作按钮 -->
            <div class="col-md-3 col-sm-6 col-xs-12 flex items-center">
              <q-btn
                type="submit"
                color="primary"
                :label="$q.screen.gt.xs ? '查询' : ''"
                icon="search"
                :class="$q.screen.gt.xs ? 'q-mr-sm' : 'q-mr-xs'"
                :loading="state.loading"
                :dense="$q.screen.lt.md"
              />
              <q-btn
                @click="resetQuery"
                :label="$q.screen.gt.xs ? '重置' : ''"
                outline
                color="primary"
                icon="refresh"
                :class="$q.screen.gt.xs ? 'q-mr-sm' : 'q-mr-xs'"
                :dense="$q.screen.lt.md"
              />
            </div>
          </q-form>
        </q-card-section>
      </q-slide-transition>
    </q-card>

    <!-- 操作按钮和表格 -->
    <q-card flat bordered>
      <q-card-section class="row items-center bg-grey-2">
        <!-- 左侧：操作按钮 -->
        <div class="col-auto q-gutter-x-sm">
          <q-btn
            color="primary"
            :label="$q.screen.gt.xs ? '新增角色' : ''"
            icon="add"
            @click="openCreateDialog"
            :loading="state.loading"
            dense
          />
          <q-btn
            color="negative"
            :label="$q.screen.gt.xs ? '批量删除' : ''"
            icon="delete"
            :disable="state.selected.length === 0"
            @click="handleBatchDelete"
            :loading="state.loading"
            dense
          />
          <q-btn
            color="grey"
            :label="$q.screen.gt.xs ? '导出数据' : ''"
            icon="file_download"
            dense
          />
        </div>

        <!-- 右侧：表格操作按钮 -->
        <RightToolBar v-model:search="state.search" :columns="columns" @refresh="refreshTable" />
      </q-card-section>

      <!-- 数据表格 -->
      <q-table
        v-model:selected="state.selected"
        :rows="state.roles"
        :columns="visibleColumns"
        row-key="id"
        :loading="state.loading"
        binary-state-sort
        flat
        bordered
        selection="multiple"
        v-model:pagination="pagination"
        :rows-per-page-options="[10, 20, 50, 100, { label: '全部', value: 0 }]"
        @request="onRequest"
      >
        <!-- 序号列自定义 -->
        <template v-slot:body-cell-index="props">
          <q-td :props="props">
            {{ props.rowIndex + 1 }}
          </q-td>
        </template>

        <!-- 状态列自定义 -->
        <template v-slot:body-cell-status="props">
          <q-td :props="props">
            <q-toggle
              :model-value="props.row.status"
              checked-icon="check"
              unchecked-icon="clear"
              true-value="0"
              false-value="1"
              color="green"
              @update:model-value="toggleStatus(props.row, $event)"
            />
          </q-td>
        </template>

        <!-- 操作列 -->
        <template v-slot:body-cell-actions="props">
          <q-td :props="props" class="q-gutter-x-xs">
            <q-btn
              dense
              color="primary"
              icon="edit"
              @click="openEditDialog(props.row)"
              :loading="state.loading"
            >
              <q-tooltip>编辑</q-tooltip>
            </q-btn>
            <q-btn
              dense
              color="secondary"
              icon="menu"
              @click="openMenuPermissionDialog(props.row)"
              :loading="state.loading"
            >
              <q-tooltip>菜单权限</q-tooltip>
            </q-btn>
            <q-btn
              dense
              color="info"
              icon="storage"
              @click="openDataPermissionDialog(props.row)"
              :loading="state.loading"
            >
              <q-tooltip>数据权限</q-tooltip>
            </q-btn>
            <q-btn
              dense
              color="negative"
              icon="delete"
              @click="handleDelete(props.row)"
              :loading="state.loading"
            >
              <q-tooltip>删除</q-tooltip>
            </q-btn>
          </q-td>
        </template>
      </q-table>
    </q-card>

    <!-- 新增/更新对话框 -->
    <CreateOrUpdateRoleDialog
      v-model="state.dialogs.createOrUpdate"
      :role-id="state.currentId"
      :operate="state.operate"
      @success="refreshTable"
    />

    <!-- 菜单权限分配对话框 -->
    <MenuPermissionDialog v-model="state.dialogs.menuPermission" :role-id="state.currentId" />

    <!-- 数据权限分配对话框 -->
    <DataPermissionDialog v-model="state.dialogs.dataPermission" :role-id="state.currentId" />
  </q-page>
</template>

<script setup>
import modal from '@/plugins/modal'
import { changeRoleStatus, delRole, listRole, batchDelRole } from '@/api/sys/role'
import DataPermissionDialog from './components/DataPermissionDialog'
import MenuPermissionDialog from './components/MenuPermissionDialog'
import CreateOrUpdateRoleDialog from './components/CreateOrUpdateRoleDialog'

const { proxy } = getCurrentInstance()

// 统一状态管理
const state = reactive({
  roles: [],
  selected: [],
  loading: false,
  search: false,
  currentId: undefined,
  operate: 'create',
  dialogs: {
    createOrUpdate: false,
    menuPermission: false,
    dataPermission: false,
  },
})

// 状态选项
const statusOptions = [
  { label: '全部', value: null },
  { label: '启用', value: 1 },
  { label: '禁用', value: 0 },
]

// 分页配置
const pagination = ref({
  page: 1,
  rowsPerPage: 10,
  rowsNumber: 0,
})

// 查询参数
const queryParams = reactive({
  name: '',
  key: '',
  status: null,
})

// 表格列定义
const columns = ref([
  { name: 'selection', align: 'center', sortable: false },
  { name: 'index', label: '序号', align: 'center', sortable: false, visible: true },
  {
    name: 'name',
    label: '角色名称',
    field: 'name',
    align: 'center',
    sortable: true,
    visible: true,
  },
  { name: 'key', label: '角色标识', field: 'key', align: 'center', sortable: true, visible: true },
  { name: 'sort', label: '排序', field: 'sort', align: 'center', sortable: true, visible: true },
  { name: 'status', label: '状态', field: 'status', align: 'center', visible: true },
  {
    name: 'create_time',
    label: '创建时间',
    field: 'create_time',
    align: 'center',
    sortable: true,
    visible: true,
  },
  { name: 'remark', label: '备注', field: 'remark', align: 'center', visible: true },
  { name: 'actions', label: '操作', align: 'center', visible: true },
])

// 计算属性：可见列
const visibleColumns = computed(() => columns.value.filter((col) => col.visible))

// 初始化加载数据
onMounted(() => {
  fetchRoles()
})

// 获取角色列表
const fetchRoles = async () => {
  state.loading = true
  try {
    const params = {
      ...queryParams,
      page: pagination.value.rowsPerPage === 0 ? 1 : pagination.value.page,
      limit: pagination.value.rowsPerPage === 0 ? 0 : pagination.value.rowsPerPage,
    }

    const res = await listRole(params)
    state.roles = res.data
    pagination.value.rowsNumber =
      pagination.value.rowsPerPage === 0 ? state.roles.length : res.total
  } catch (error) {
    modal.msgError('加载角色列表失败')
  } finally {
    state.loading = false
  }
}

// 表格请求处理
const onRequest = async ({ pagination: newPagination }) => {
  Object.assign(pagination.value, newPagination)
  await fetchRoles()
}

// 查询处理
const handleQuery = () => {
  pagination.value.page = 1
  fetchRoles()
}

// 重置查询
const resetQuery = () => {
  Object.assign(queryParams, {
    name: '',
    key: '',
    status: null,
  })
  handleQuery()
}

// 刷新表格
const refreshTable = () => {
  fetchRoles()
}

// 对话框操作
const openDialog = (type, id = null, operate = 'create') => {
  state.currentId = id
  state.operate = operate
  state.dialogs[type] = true
}

const openCreateDialog = () => openDialog('createOrUpdate', null, 'create')
const openEditDialog = (row) => openDialog('createOrUpdate', row.id, 'update')
const openMenuPermissionDialog = (row) => openDialog('menuPermission', row.id)
const openDataPermissionDialog = (row) => openDialog('dataPermission', row.id)

// 切换角色状态
const toggleStatus = async (row, newStatus) => {
  const action = newStatus === '0' ? '启用' : '禁用'
  try {
    state.loading = true
    await changeRoleStatus(row)
    row.status = newStatus
    modal.msgSuccess(` 角色已${action}`)
  } catch (error) {
    modal.msgError(`${action} 角色失败！`)
    row.status = row.status === 1 ? 0 : 1
  } finally {
    state.loading = false
  }
}

// 删除角色
const handleDelete = (row) => {
  modal.confirm({
    title: '删除确认',
    message: `确定要删除角色 "${row.name}"  吗？此操作不可恢复！`,
    action: async () => {
      state.loading = true
      try {
        await delRole(row.id)
        state.selected = state.selected.filter((role) => role?.id === 'aaa')
        modal.msgSuccess(`成功删除角色 "${row.name}"！`)
        refreshTable()
      } catch (error) {
        modal.msgError('删除角色失败！')
      } finally {
        state.loading = false
      }
    },
  })
}

// 批量删除
const handleBatchDelete = () => {
  if (state.selected.length === 0) {
    modal.msgWarning('请先选择要删除的角色！')
    return
  }
  modal.confirm({
    title: '批量删除确认',
    message: `确定要删除选中的 ${state.selected.length} 个角色吗？此操作不可恢复！`,
    action: async () => {
      state.loading = true
      try {
        const ids = state.selected.map((role) => role.id)
        await batchDelRole(ids)
        modal.msgSuccess(`成功删除 ${ids.length} 个角色！`)
        state.selected = []
        refreshTable()
      } catch (error) {
        modal.msgError('删除角色失败！')
      } finally {
        state.loading = false
      }
    },
  })
}
</script>
